package com.tianlh.service.impl.redis.ReentrantLock;

import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.Lock;

/**
 * @author 黑子
 * @Date 2018/1/11 16:16
 */
public abstract class AbstractLock implements Lock {

    /**
     *
     * 同一个jvm的多个线程使用同一个锁对象, 那可见性就必须要保证了.
     *
     */

    protected volatile boolean locked;

    /**
     * 阻塞性的获取锁, 不响应中断
     */
    @Override
    public void lock() {
        try {
            lock(false, 0, null, false);
        } catch (InterruptedException e) {
            // TODO ignore
        }
    }

    /**
     * 阻塞性的获取锁, 响应中断
     *
     * @throws InterruptedException
     */
    @Override
    public void lockInterruptibly() throws InterruptedException {
        lock(false, 0, null, true);
    }

    /**
     * 超时自动返回的阻塞性的获取锁, 不响应中断
     *
     * @param time
     * @param unit
     * @return {@code true} 若成功获取到锁, {@code false} 若在指定时间内未获取到锁
     *
     */
    @Override
    public boolean tryLock(long time, TimeUnit unit) {
        try {
            return lock(true, time, unit, false);
        } catch (InterruptedException e) {
            // TODO ignore
        }
        return false;
    }

    /**
     * 释放锁
     */
    @Override
    public void unlock() {
        unlock0();
    }

    protected abstract void unlock0();

    protected abstract boolean lock(boolean useTimeout, long time, TimeUnit unit, boolean interrupt) throws InterruptedException;


}
